package com.pdg.mcplugin.common.baseclasses;

import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;

import org.bukkit.command.CommandSender;

import com.pdg.mcplugin.common.ArgumentList;
import com.pdg.mcplugin.common.interfaces.CommandProcessor;

public abstract class CommandProcessorBase<E extends PluginBase> extends PluginClientBase<E> implements CommandProcessor{

	private String[] helpText;
	private boolean defaultCommandHelp;
	
	private void setHelpText(String[] theHelpText){
		helpText = theHelpText;
	}
	
	private String[] getHelpText(){
		return helpText;
	}
	
	private Map<String,CommandProcessorBase<E>> subProcessors = new HashMap<String,CommandProcessorBase<E>>();
	
	protected void setSubProcessor(String theKey, CommandProcessorBase<E> theSubProcessor){
		if(theSubProcessor==null){
			subProcessors.remove(theKey);
		}else{
			subProcessors.put(theKey, theSubProcessor);
		}
	}
	private CommandProcessorBase<E> getSubProcessor(String theKey){
		return subProcessors.get(theKey);
	}
	
	public CommandProcessorBase(E thePlugin,String[] theHelpText) {
		this(thePlugin,theHelpText,true);
	}

	public CommandProcessorBase(E thePlugin,String[] theHelpText,boolean isDefaultCommandHelp) {
		super(thePlugin);
		setHelpText(theHelpText);
		setDefaultCommandHelp(isDefaultCommandHelp);
	}
	
	protected abstract boolean specialProcessCommand(CommandSender theCommandSender,String theSubCommand, ArgumentList theArgumentList);
	
	public boolean processCommand(CommandSender theCommandSender,
			ArgumentList theArgumentList) {
		String subcommand = null;
		try{
			subcommand = theArgumentList.pop();
		}catch(StackOverflowError e){
			subcommand = null;
		}
		if(subcommand==null){
			if(isDefaultCommandHelp()){
				showHelp(theCommandSender);
			}else{
				showDefault(theCommandSender);
			}
		}else{
			Iterator<String> keys = subProcessors.keySet().iterator();
			while(keys.hasNext()){
				String theKey = keys.next();
				if(subcommand.equalsIgnoreCase(theKey)){
					return getSubProcessor(theKey).processCommand(theCommandSender, theArgumentList);
				}
			}
			if(!specialProcessCommand(theCommandSender,subcommand,theArgumentList)){
				showHelp(theCommandSender);
			}
		}
		return true;		
	}
	
	protected void showDefault(CommandSender theCommandSender){
		
	}

	protected void showHelp(CommandSender theCommandSender) {
		for(int index=0;index<helpText.length;++index){
			getPlugin().sendInformationalMessage(theCommandSender, getHelpText()[index]);
		}
	}

	private boolean isDefaultCommandHelp() {
		return defaultCommandHelp;
	}

	private void setDefaultCommandHelp(boolean defaultCommandHelp) {
		this.defaultCommandHelp = defaultCommandHelp;
	}


}
